hvmloader: Expand iomem allocation pool to 0xf0000000-0xfc000000.
authorKeir Fraser <keir.fraser@citrix.com>
Tue, 22 Jan 2008 11:18:10 +0000 (11:18 +0000)
committerKeir Fraser <keir.fraser@citrix.com>
Tue, 22 Jan 2008 11:18:10 +0000 (11:18 +0000)
Check for exhaustion of allocation pool, warn user, and fail to
initialise the relevant PCI BAR.

Signed-off-by: Keir Fraser <keir.fraser@citrix.com>
tools/firmware/hvmloader/acpi/build.c
tools/firmware/hvmloader/hvmloader.c

index 1323b17065a6bc6b065e560b7789f5cc13c280b9..247c3b5928b3d64bf839aea04a2b9887b171aa7c 100644 (file)
@@ -76,7 +76,7 @@ static int construct_bios_info_table(uint8_t *buf)
     bios_info->com2_present = uart_exists(0x2f8);
 
     bios_info->pci_min = 0xf0000000;
-    bios_info->pci_len = 0x05000000;
+    bios_info->pci_len = 0x0c000000;
 
     return align16(sizeof(*bios_info));
 }
index 59c6e74512ce2d79fb0329a5b2af1100cbf2c589..ce6f8a063c0278b057c1edbbaec0d856acec5dda 100644 (file)
@@ -183,11 +183,17 @@ static void apic_setup(void)
 
 static void pci_setup(void)
 {
-    uint32_t devfn, bar_reg, bar_data, bar_sz, cmd;
-    uint32_t *base, io_base = 0xc000, mem_base = HVM_BELOW_4G_MMIO_START;
+    uint32_t base, devfn, bar_reg, bar_data, bar_sz, cmd;
     uint16_t class, vendor_id, device_id;
     unsigned int bar, pin, link, isa_irq;
 
+    /* Resources assignable to PCI devices via BARs. */
+    struct resource {
+        uint32_t base, max;
+    } *resource;
+    struct resource mem_resource = { 0xf0000000, 0xfc000000 };
+    struct resource io_resource  = { 0xc000, 0x10000 };
+
     /* Create a list of device BARs in descending order of size. */
     struct bars {
         uint32_t devfn, bar_reg, bar_sz;
@@ -301,22 +307,31 @@ static void pci_setup(void)
         if ( (bar_data & PCI_BASE_ADDRESS_SPACE) ==
              PCI_BASE_ADDRESS_SPACE_MEMORY )
         {
-            base = &mem_base;
+            resource = &mem_resource;
             bar_data &= ~PCI_BASE_ADDRESS_MEM_MASK;
         }
         else
         {
-            base = &io_base;
+            resource = &io_resource;
             bar_data &= ~PCI_BASE_ADDRESS_IO_MASK;
         }
 
-        *base = (*base + bar_sz - 1) & ~(bar_sz - 1);
-        bar_data |= *base;
-        *base += bar_sz;
+        base = (resource->base + bar_sz - 1) & ~(bar_sz - 1);
+        bar_data |= base;
+        base += bar_sz;
+
+        if ( (base < resource->base) || (base > resource->max) )
+        {
+            printf("pci dev %02x:%x bar %02x size %08x: no space for "
+                   "resource!\n", devfn>>3, devfn&7, bar_reg, bar_sz);
+            continue;
+        }
+
+        resource->base = base;
 
         pci_writel(devfn, bar_reg, bar_data);
-        printf("pci dev %02x:%x bar %02x size %08x: %08x %08x/%08x\n",
-               devfn>>3, devfn&7, bar_reg, bar_sz, bar_data, i, nr_bars);
+        printf("pci dev %02x:%x bar %02x size %08x: %08x\n",
+               devfn>>3, devfn&7, bar_reg, bar_sz, bar_data);
 
         /* Now enable the memory or I/O mapping. */
         cmd = pci_readw(devfn, PCI_COMMAND);